﻿//-----------------------------------------------------------------------
// <copyright file="DialogControl.cs" company="Noboru Project">
//      Copyright (c) Noboru Project. All rights reserved.
//
//      This source code is subject to terms and conditions of the New BSD License (BSD).
//      A copy of the license can be found in the License.html file at the root of this 
//      distribution. If you can not locate the New BSD License (BSD), please send an 
//      email to noboru_adm@live.com.
//      By using this source code in any fashion, you are agreeing to be bound by
//      the terms of the New BSD License (BSD) for Noboru.
//
//      You must not remove this notice, or any other, from this software.
// </copyright>
//-----------------------------------------------------------------------

using System;
using System.ComponentModel;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Controls.Primitives;
using System.Windows.Documents;
using System.Windows.Ink;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;

namespace Noboru.Windows.Controls
{
    /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.Class"]/*' />
    [TemplatePart(Name = "BackgroundPart", Type = typeof(Canvas))]
    [TemplatePart(Name = "DialogPart", Type = typeof(FrameworkElement))]
    [TemplatePart(Name = "DialogCloseButtonPart", Type = typeof(FrameworkElement))]
    [TemplatePart(Name = "TitleBarPart", Type = typeof(FrameworkElement))]
    [TemplatePart(Name = "TitleTextPart", Type = typeof(TextBlock))]
    [TemplatePart(Name = "TitleImagePart", Type = typeof(Image))]
    [TemplateVisualState(Name = "DialogCloseButtonNormal", GroupName = "DialogCloseButtonStates")]
    [TemplateVisualState(Name = "DialogCloseButtonMouseOver", GroupName = "DialogCloseButtonStates")]
    [TemplateVisualState(Name = "DialogCloseButtonMouseLeftButtonDown", GroupName = "DialogCloseButtonStates")]
    [TemplateVisualState(Name = "DialogNotModal", GroupName = "DialogModalStates")]
    [TemplateVisualState(Name = "DialogModal", GroupName = "DialogModalStates")]
    [TemplateVisualState(Name = "DialogModalGray", GroupName = "DialogModalStates")]
    [TemplateVisualState(Name = "Focused", GroupName = "FocusStates")]
    [TemplateVisualState(Name = "Unfocused", GroupName = "FocusStates")]
    public class DialogControl : ContentControl
    {
        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.DisplayImageProperty"]/*'/>
        public static readonly DependencyProperty DisplayImageProperty = DependencyProperty.Register("DisplayImage", typeof(bool), typeof(DialogControl), new PropertyMetadata(false, DialogControl.PropertyChangedCallback));

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.DialogResultProperty"]/*'/>
        public static readonly DependencyProperty DialogResultProperty = DependencyProperty.Register("DialogResult", typeof(DialogResult), typeof(DialogControl), new PropertyMetadata(DialogResult.None, DialogControl.PropertyChangedCallback));

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.ImageSourceProperty"]/*'/>
        public static readonly DependencyProperty ImageSourceProperty = DependencyProperty.Register("ImageSource", typeof(ImageSource), typeof(DialogControl), new PropertyMetadata(DialogControl.PropertyChangedCallback));

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.OpenPositionProperty"]/*'/>
        public static readonly DependencyProperty OpenPositionProperty = DependencyProperty.Register("OpenPosition", typeof(DialogOpenPosition), typeof(DialogControl), new PropertyMetadata(DialogOpenPosition.Center));

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.ModalProperty"]/*'/>
        public static readonly DependencyProperty ModalProperty = DependencyProperty.Register("Modal", typeof(DialogModal), typeof(DialogControl), new PropertyMetadata(DialogModal.NotModal, DialogControl.PropertyChangedCallback));

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.TitleProperty"]/*'/>
        public static readonly DependencyProperty TitleProperty = DependencyProperty.Register("Title", typeof(string), typeof(DialogControl), new PropertyMetadata("Dialog control title", DialogControl.PropertyChangedCallback));

        private bool _isDragging;
        private bool _isMouseOverClose;
        private bool _isMouseLeftButtonDownClose;
        ////private bool _hasFocus; // Used in future removed to remove code analysis warning
        private Popup _popup;
        private Canvas _backgroundPart;
        private TextBlock _titleTextPart;
        private Image _titleImagePart;
        private FrameworkElement _dialogPart;
        private FrameworkElement _titleBarPart;
        private FrameworkElement _dialogCloseButtonPart;
        private Point _lastPoint;

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.Constructor"]/*'/>
        public DialogControl()
        {
            this.DefaultStyleKey = typeof(DialogControl);
        }

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.Closed"]/*'/>
        public event EventHandler Closed;

        public event EventHandler<CancelEventArgs> Closing;

        public bool DisplayImage
        {
            get
            {
                return (bool)this.GetValue(DisplayImageProperty);
            }

            set
            {
                this.SetValue(DisplayImageProperty, value);
            }
        }

        public DialogResult DialogResult
        {
            get
            {
                return (DialogResult)this.GetValue(DialogResultProperty);
            }

            set
            {
                this.SetValue(DialogResultProperty, value);
            }
        }

        public ImageSource ImageSource
        {
            get
            {
                return (ImageSource)this.GetValue(ImageSourceProperty);
            }

            set
            {
                this.SetValue(ImageSourceProperty, value);
            }
        }

        public DialogOpenPosition OpenPosition
        {
            get
            {
                return (DialogOpenPosition)this.GetValue(OpenPositionProperty);
            }

            set
            {
                this.SetValue(OpenPositionProperty, value);
            }
        }

        public DialogModal Modal
        {
            get
            {
                return (DialogModal)this.GetValue(ModalProperty);
            }

            set
            {
                this.SetValue(ModalProperty, value);
            }
        }

        public string Title
        {
            get
            {
                return (string)this.GetValue(TitleProperty);
            }

            set
            {
                this.SetValue(TitleProperty, value);
            }
        }

        private FrameworkElement DialogCloseButtonPart
        {
            get
            {
                return this._dialogCloseButtonPart;
            }

            set
            {
                FrameworkElement oldDialogCloseButtonPart = this._dialogCloseButtonPart;
                if (oldDialogCloseButtonPart != null)
                {
                    oldDialogCloseButtonPart.MouseEnter -= new MouseEventHandler(this.DialogCloseButtonPart_MouseEnter);
                    oldDialogCloseButtonPart.MouseLeave -= new MouseEventHandler(this.DialogCloseButtonPart_MouseLeave);
                    oldDialogCloseButtonPart.MouseLeftButtonDown -= new MouseButtonEventHandler(this.DialogCloseButtonPart_MouseLeftButtonDown);
                    oldDialogCloseButtonPart.MouseLeftButtonUp -= new MouseButtonEventHandler(this.DialogCloseButtonPart_MouseLeftButtonUp);
                }

                this._dialogCloseButtonPart = value;

                if (this._dialogCloseButtonPart != null)
                {
                    this._dialogCloseButtonPart.MouseEnter += new MouseEventHandler(this.DialogCloseButtonPart_MouseEnter);
                    this._dialogCloseButtonPart.MouseLeave += new MouseEventHandler(this.DialogCloseButtonPart_MouseLeave);
                    this._dialogCloseButtonPart.MouseLeftButtonDown += new MouseButtonEventHandler(this.DialogCloseButtonPart_MouseLeftButtonDown);
                    this._dialogCloseButtonPart.MouseLeftButtonUp += new MouseButtonEventHandler(this.DialogCloseButtonPart_MouseLeftButtonUp);
                }
            }
        }

        private FrameworkElement DialogPart
        {
            get
            {
                return this._dialogPart;
            }

            set
            {
                FrameworkElement oldDialogPart = this._dialogPart;
                if (oldDialogPart != null)
                {
                    oldDialogPart.GotFocus -= new RoutedEventHandler(this.DialogPart_GotFocus);
                    oldDialogPart.LostFocus -= new RoutedEventHandler(this.DialogPart_LostFocus);
                    oldDialogPart.MouseLeftButtonDown -= new MouseButtonEventHandler(this.DialogPart_MouseLeftButtonDown);
                    ////oldDialogPart.MouseEnter -= new MouseEventHandler(this.dialogPart_MouseEnter);
                    ////oldDialogPart.MouseLeave -= new MouseEventHandler(this.dialogPart_MouseLeave);
                    ////oldDialogPart.MouseLeftButtonUp -= new MouseButtonEventHandler(this.dialogPart_MouseLeftButtonUp);
                }

                this._dialogPart = value;

                if (this._dialogPart != null)
                {
                    this._dialogPart.GotFocus += new RoutedEventHandler(this.DialogPart_GotFocus);
                    this._dialogPart.LostFocus += new RoutedEventHandler(this.DialogPart_LostFocus);
                    this._dialogPart.MouseLeftButtonDown += new MouseButtonEventHandler(this.DialogPart_MouseLeftButtonDown);
                    ////this._dialogPart.MouseEnter += new MouseEventHandler(this.dialogPart_MouseEnter);
                    ////this._dialogPart.MouseLeave += new MouseEventHandler(this.dialogPart_MouseLeave);
                    ////this._dialogPart.MouseLeftButtonUp += new MouseButtonEventHandler(this.dialogPart_MouseLeftButtonUp);                  
                }
            }
        }

        private FrameworkElement TitleBarPart
        {
            get
            {
                return this._titleBarPart;
            }

            set
            {
                FrameworkElement oldDialogTitlePart = this._titleBarPart;
                if (oldDialogTitlePart != null)
                {
                    oldDialogTitlePart.MouseEnter -= new MouseEventHandler(this.TitleBarPart_MouseEnter);
                    oldDialogTitlePart.MouseLeave -= new MouseEventHandler(this.TitleBarPart_MouseLeave);
                    oldDialogTitlePart.MouseMove -= new MouseEventHandler(this.TitleBarPart_MouseMove);
                    oldDialogTitlePart.MouseLeftButtonDown -= new MouseButtonEventHandler(this.TitleBarPart_MouseLeftButtonDown);
                    oldDialogTitlePart.MouseLeftButtonUp -= new MouseButtonEventHandler(this.TitleBarPart_MouseLeftButtonUp);
                }

                this._titleBarPart = value;

                if (this._dialogPart != null)
                {
                    this._titleBarPart.MouseEnter += new MouseEventHandler(this.TitleBarPart_MouseEnter);
                    this._titleBarPart.MouseLeave += new MouseEventHandler(this.TitleBarPart_MouseLeave);
                    this._titleBarPart.MouseMove += new MouseEventHandler(this.TitleBarPart_MouseMove);
                    this._titleBarPart.MouseLeftButtonDown += new MouseButtonEventHandler(this.TitleBarPart_MouseLeftButtonDown);
                    this._titleBarPart.MouseLeftButtonUp += new MouseButtonEventHandler(this.TitleBarPart_MouseLeftButtonUp);
                }
            }
        }

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.Close"]/*'/>
        public void Close()
        {
            CancelEventArgs cancelEventArgs = new CancelEventArgs();
            this.OnClosing(cancelEventArgs);
        }

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.Show"]/*'/>
        public void Show()
        {
            this.InitializeComponent();

            ////this._hasFocus = true;
            this._popup.Child = this;
            this._popup.IsOpen = true;
        }

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.ShowModal"]/*'/>
        public void ShowModal()
        {
            this.Modal = DialogModal.Modal;
            this.Show();
        }

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.ShowModalGrayed"]/*'/>
        public void ShowModal(bool grayed)
        {
            if (grayed)
            {
                this.Modal = DialogModal.ModalGray;
            }
            else
            {
                this.Modal = DialogModal.Modal;
            }

            this.Show();
        }

        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.OnApplyTemplate"]/*'/>
        public override void OnApplyTemplate()
        {
            base.OnApplyTemplate();

            this._backgroundPart = (Canvas)GetTemplateChild("BackgroundPart");
            this.DialogPart = (FrameworkElement)GetTemplateChild("DialogPart");
            this.TitleBarPart = (FrameworkElement)GetTemplateChild("TitleBarPart");
            this.DialogCloseButtonPart = (FrameworkElement)GetTemplateChild("DialogCloseButtonPart");
            this._titleTextPart = (TextBlock)GetTemplateChild("TitleTextPart");
            this._titleImagePart = (Image)GetTemplateChild("TitleImagePart");

            if (string.IsNullOrEmpty(this.Title))
            {
                this._titleTextPart.Text = "  ";
            }
            else
            {
                this._titleTextPart.Text = this.Title;
            }

            if (this.DisplayImage)
            {
                this._titleImagePart.Visibility = Visibility.Visible;
            }

            if (this.ImageSource != null)
            {
                this._titleImagePart.Source = this.ImageSource;
            }

            this.DetermineLayout();
            this.GoToState(false);

            Application.Current.Host.Content.Resized += new EventHandler(this.ParentContentResized);
        }
       
        /// <include file='Documentation\DialogControlDocumentation.uex' path='Members/Member[@for="DialogControl.OnClosed"]/*'/>
        protected virtual void OnClosed(EventArgs e)
        {
            if (this.Closed != null)
            {
                this.Closed(this, e);
            }

            if (this._popup != null)
            {
                if (this._popup.IsOpen)
                {
                    this._popup.IsOpen = false;
                }
            }
        }

        protected virtual void OnClosing(CancelEventArgs e)
        {
            if (this.Closing != null)
            {
                this.Closing(this, e);
            }

            if (e != null)
            {
                if (!e.Cancel)
                {
                    this.OnClosed(EventArgs.Empty);
                }
            }
        }

        private static void CenterControl(FrameworkElement element, Canvas parent)
        {
            if (element.ActualHeight == 0 || double.IsNaN(element.ActualHeight))
            {
                if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
                {
                    element.Measure(new Size(parent.ActualWidth, parent.ActualHeight));
                }
                else
                {
                    element.Measure(new Size(parent.Width, parent.Height));
                }
            }

            if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling((parent.ActualHeight / 2) - (element.DesiredSize.Height / 2)));
                element.SetValue(Canvas.LeftProperty, Math.Ceiling((parent.ActualWidth / 2) - (element.DesiredSize.Width / 2)));
            }
            else
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling((parent.Height / 2) - (element.DesiredSize.Height / 2)));
                element.SetValue(Canvas.LeftProperty, Math.Ceiling((parent.Width / 2) - (element.DesiredSize.Width / 2)));
            }
        }

        private static void CenterBottomControl(FrameworkElement element, Canvas parent)
        {
            if (element.ActualHeight == 0 || double.IsNaN(element.ActualHeight))
            {
                if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
                {
                    element.Measure(new Size(parent.ActualWidth, parent.ActualHeight));
                }
                else
                {
                    element.Measure(new Size(parent.Width, parent.Height));
                }
            }

            if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling(parent.ActualHeight - element.DesiredSize.Height));
                element.SetValue(Canvas.LeftProperty, Math.Ceiling((parent.ActualWidth / 2) - (element.DesiredSize.Width / 2)));
            }
            else
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling(parent.Height - element.DesiredSize.Height));
                element.SetValue(Canvas.LeftProperty, Math.Ceiling((parent.Width / 2) - (element.DesiredSize.Width / 2)));
            }
        }

        private static void CenterTopControl(FrameworkElement element, Canvas parent)
        {
            if (element.ActualHeight == 0 || double.IsNaN(element.ActualHeight))
            {
                if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
                {
                    element.Measure(new Size(parent.ActualWidth, parent.ActualHeight));
                }
                else
                {
                    element.Measure(new Size(parent.Width, parent.Height));
                }
            }

            if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
            {
                element.SetValue(Canvas.LeftProperty, Math.Ceiling((parent.ActualWidth / 2) - (element.DesiredSize.Width / 2)));
            }
            else
            {
                element.SetValue(Canvas.LeftProperty, Math.Ceiling((parent.Width / 2) - (element.DesiredSize.Width / 2)));
            }
        }

        private static void LeftTopControl(FrameworkElement element, Canvas parent)
        {
        }

        private static void LeftBottomControl(FrameworkElement element, Canvas parent)
        {
            if (element.ActualHeight == 0 || double.IsNaN(element.ActualHeight))
            {
                if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
                {
                    element.Measure(new Size(parent.ActualWidth, parent.ActualHeight));
                }
                else
                {
                    element.Measure(new Size(parent.Width, parent.Height));
                }
            }

            if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling(parent.ActualHeight - element.DesiredSize.Height));
            }
            else
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling(parent.Height - element.DesiredSize.Height));
            }
        }

        private static void LeftCenterControl(FrameworkElement element, Canvas parent)
        {
            if (element.ActualHeight == 0 || double.IsNaN(element.ActualHeight))
            {
                if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
                {
                    element.Measure(new Size(parent.ActualWidth, parent.ActualHeight));
                }
                else
                {
                    element.Measure(new Size(parent.Width, parent.Height));
                }
            }

            if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling((parent.ActualHeight / 2) - (element.DesiredSize.Height / 2)));
            }
            else
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling((parent.Height / 2) - (element.DesiredSize.Height / 2)));
            }
        }

        private static void RightTopControl(FrameworkElement element, Canvas parent)
        {
            if (element.ActualHeight == 0 || double.IsNaN(element.ActualHeight))
            {
                if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
                {
                    element.Measure(new Size(parent.ActualWidth, parent.ActualHeight));
                }
                else
                {
                    element.Measure(new Size(parent.Width, parent.Height));
                }
            }

            if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
            {
                element.SetValue(Canvas.LeftProperty, Math.Ceiling(parent.ActualWidth - element.DesiredSize.Width));
            }
            else
            {
                element.SetValue(Canvas.LeftProperty, Math.Ceiling(parent.Width - element.DesiredSize.Width));
            }
        }

        private static void RightCenterControl(FrameworkElement element, Canvas parent)
        {
            if (element.ActualHeight == 0 || double.IsNaN(element.ActualHeight))
            {
                if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
                {
                    element.Measure(new Size(parent.ActualWidth, parent.ActualHeight));
                }
                else
                {
                    element.Measure(new Size(parent.Width, parent.Height));
                }
            }

            if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling((parent.ActualHeight / 2) - (element.DesiredSize.Height / 2)));
                element.SetValue(Canvas.LeftProperty, Math.Ceiling(parent.ActualWidth - (element.DesiredSize.Width / 2)));
            }
            else
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling((parent.Height / 2) - (element.DesiredSize.Height / 2)));
                element.SetValue(Canvas.LeftProperty, Math.Ceiling(parent.Width - element.DesiredSize.Width));
            }
        }

        private static void RightBottomControl(FrameworkElement element, Canvas parent)
        {
            if (element.ActualHeight == 0 || double.IsNaN(element.ActualHeight))
            {
                if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
                {
                    element.Measure(new Size(parent.ActualWidth, parent.ActualHeight));
                }
                else
                {
                    element.Measure(new Size(parent.Width, parent.Height));
                }
            }

            if (parent.ActualWidth > 0 && parent.ActualHeight > 0)
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling(parent.ActualHeight - element.DesiredSize.Height));
                element.SetValue(Canvas.LeftProperty, Math.Ceiling(parent.ActualWidth - element.DesiredSize.Width));
            }
            else
            {
                element.SetValue(Canvas.TopProperty, Math.Ceiling(parent.Height - element.DesiredSize.Height));
                element.SetValue(Canvas.LeftProperty, Math.Ceiling(parent.Width - element.DesiredSize.Width));
            }
        }

        private static void PropertyChangedCallback(DependencyObject sender, DependencyPropertyChangedEventArgs e)
        {
            ((DialogControl)sender).OnPropertyChanged(e);
        }

        private void DialogPart_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
        {
            ////this._backgroundPart.SetValue(Canvas.ZIndexProperty, 100); 
        }

        private void DialogPart_GotFocus(object sender, RoutedEventArgs e)
        {
            ////this._hasFocus = true;
            this.GoToState(false);
        }

        private void DialogPart_LostFocus(object sender, RoutedEventArgs e)
        {
            ////this._hasFocus = false;
            this.GoToState(false);
        }

        private void OnPropertyChanged(DependencyPropertyChangedEventArgs e)
        {
            if (this._titleTextPart != null)
            {
                if (string.IsNullOrEmpty(this.Title))
                {
                    this._titleTextPart.Text = "  ";
                }
                else
                {
                    this._titleTextPart.Text = this.Title;
                }
            }

            if (this._titleImagePart != null)
            {
                if (this.ImageSource != null)
                {
                    this._titleImagePart.Source = this.ImageSource;
                }

                if (this.DisplayImage && (this._titleImagePart.Visibility == Visibility.Collapsed))
                {
                    this._titleImagePart.Visibility = Visibility.Visible;
                }
                else if (this._titleImagePart.Visibility == Visibility.Visible)
                {
                    this._titleImagePart.Visibility = Visibility.Collapsed;
                }
            }
        }

        private void DialogCloseButtonPart_MouseEnter(object sender, MouseEventArgs e)
        {
            this._isMouseOverClose = true;
            this.GoToState(true);
        }

        private void DialogCloseButtonPart_MouseLeave(object sender, MouseEventArgs e)
        {
            this._isMouseOverClose = false;
            this.GoToState(true);
        }

        private void DialogCloseButtonPart_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
        {
            this._dialogCloseButtonPart.CaptureMouse();
            this._isMouseLeftButtonDownClose = true;
            this.GoToState(true);
        }

        private void DialogCloseButtonPart_MouseLeftButtonUp(object sender, MouseButtonEventArgs e)
        {
            this._isMouseLeftButtonDownClose = false;
            this._dialogCloseButtonPart.ReleaseMouseCapture();

            if (this._isMouseOverClose)
            {
                this.Close();
            }
        }

        private void GoToState(bool useTransitions)
        {
            if (this._isMouseOverClose)
            {
                if (this._isMouseLeftButtonDownClose)
                {
                    VisualStateManager.GoToState(this, "DialogCloseButtonMouseLeftButtonDown", useTransitions);
                }
                else
                {
                    VisualStateManager.GoToState(this, "DialogCloseButtonMouseOver", useTransitions);
                }
            }
            else
            {
                VisualStateManager.GoToState(this, "DialogCloseButtonNormal", useTransitions);
            }

            if (this.Modal == DialogModal.Modal)
            {
                this._backgroundPart.Background = new SolidColorBrush(Colors.Transparent);
            }
            else if (this.Modal == DialogModal.ModalGray)
            {
                this._backgroundPart.Background = new SolidColorBrush(Colors.Gray);
                this._backgroundPart.Background.Opacity = .3;
            }

            ////if (this._hasFocus)
            ////{
            ////    VisualStateManager.GoToState(this, "Focused", useTransitions);
            ////}
            ////else
            ////{
            ////    VisualStateManager.GoToState(this, "Unfocused", useTransitions);
            ////}
        }

        private void TitleBarPart_MouseEnter(object sender, MouseEventArgs e)
        {
        }

        private void TitleBarPart_MouseLeave(object sender, MouseEventArgs e)
        {
        }

        private void TitleBarPart_MouseMove(object sender, MouseEventArgs e)
        {
            if (true == this._isDragging)
            {
                Point pt = e.GetPosition(null);
                double x = pt.X - this._lastPoint.X;
                double y = pt.Y - this._lastPoint.Y;
                double cx = (double)this._dialogPart.GetValue(Canvas.LeftProperty);
                double cy = (double)this._dialogPart.GetValue(Canvas.TopProperty);

                this._dialogPart.SetValue(Canvas.LeftProperty, cx + x);
                this._dialogPart.SetValue(Canvas.TopProperty, cy + y);

                this._lastPoint = pt;
            }
        }

        private void TitleBarPart_MouseLeftButtonDown(object sender, MouseButtonEventArgs e)
        {
            this._titleBarPart.CaptureMouse();

            this._lastPoint = e.GetPosition(null);

            this._isDragging = true;
        }

        private void TitleBarPart_MouseLeftButtonUp(object sender, MouseButtonEventArgs e)
        {
            this._isDragging = false;
            this._titleBarPart.ReleaseMouseCapture();
        }

        private void InitializeComponent()
        {
            if (this._popup != null)
            {
                return;
            }

            this._popup = new Popup();
        }

        private void DetermineLayout()
        {
            this._backgroundPart.Width = Application.Current.Host.Content.ActualWidth;
            this._backgroundPart.Height = Application.Current.Host.Content.ActualHeight;

            this.PositionWindow();
        }

        private void PositionWindow()
        {
            if (!DesignerProperties.GetIsInDesignMode(this._dialogPart))
            {
                switch (this.OpenPosition)
                {
                    case DialogOpenPosition.TopLeft:
                        LeftTopControl(this._dialogPart, this._backgroundPart);
                        break;

                    case DialogOpenPosition.TopCenter:
                        CenterTopControl(this._dialogPart, this._backgroundPart);
                        break;

                    case DialogOpenPosition.TopRight:
                        RightTopControl(this._dialogPart, this._backgroundPart);
                        break;

                    case DialogOpenPosition.CenterLeft:
                        LeftCenterControl(this._dialogPart, this._backgroundPart);
                        break;

                    case DialogOpenPosition.Center:
                        CenterControl(this._dialogPart, this._backgroundPart);
                        break;

                    case DialogOpenPosition.CenterRight:
                        RightCenterControl(this._dialogPart, this._backgroundPart);
                        break;

                    case DialogOpenPosition.BottomLeft:
                        LeftBottomControl(this._dialogPart, this._backgroundPart);
                        break;

                    case DialogOpenPosition.BottomCenter:
                        CenterBottomControl(this._dialogPart, this._backgroundPart);
                        break;

                    case DialogOpenPosition.BottomRight:
                        RightBottomControl(this._dialogPart, this._backgroundPart);
                        break;

                    default:
                        CenterControl(this._dialogPart, this._backgroundPart);
                        break;
                }
            }
        }

        private void ParentContentResized(object sender, EventArgs e)
        {
            this.DetermineLayout();
        }
    }
}
